#!/usr/bin/env python
# -*- coding: utf-8 -*-
__author__ = 'libb@anchent.com'

# python的优势在于它的库和它的生态非常好，以至于它可以做很多事情，博主带你学习下python的内建函数和常用的模块。
# ===========================================================================================================
# 1.python的内建函数

print("*" * 100)
import sys

# print(dir(sys))  # 查看对象的属性，在学习python的模块当中可以通过dir来查看其有哪些方法
# print(help(sys))  # python的交互式帮助，在其他的编程语言中也有类似的功能，通过help可以查看模块的详细用法
a, b = 2.2, ' hello world '
print(int(a), type(a), type(int(a)))  # type用来查看对象的类型，int可以将对象强转为整数类型
print(str(a), type(str(a)))  # 将对象转换为字符串
print(len(b))  # len()方法返回对象或者序列的字符长度

file_name = 'C://test.txt'
# 打开文件，文件的处理建议使用with open() as f: pass
# print(open(file=file_name, mode='r'))  # mode:r 只读模式， w：只写模式， a：追加前提是文件中已经有内容,r+:读写模式；二进制文件b，rb，wb，rb+
print(range(3), range(0, 3))  # 返回一个整形列表，经常用于for循环中
print([i for i in range(3)], [i for i in range(3) if i % 1 == 0])  # for循环语句的简写
# input()   #等待用户在终端处输入
print(abs(-22))  # absolute 取对象的绝对值，可以将负数转为正数
import random

print(random.randint(0, 9999))  # 随机生成一个4位数的数字，例如在短信验证码中可以使用这个来生成
print(divmod(5, 2))  # 除法运算，返回商和余数
print(round(5.2222, 2))  # 返回浮点数的四舍五入，第二个参数表示小数点后几位
print(b.strip(), len(b))  # 去除字符串两端的多余空格 ' hello world ' strip() >  'hello world'
del a  # 删除对象，释放内存空间
print(max(2, 3), min(2, 3), sum((2, 3)))  # 比较字符串中最大和最小的字符
a_list, b_list = [2, 1, 0, 5], [2, 3, 5, 8]
print(a_list.sort(), a_list)  # 列表的排序
print(a_list.reverse(), a_list, a_list[::-1])  # 对象的倒叙
print(a_list)
print([print(i, j) for i, j in enumerate(a_list)])  # 返回索引位置和对应的值
print(eval("2 + 4"))  # 将字符串当成表达式求值
s = ['11', '22']
t = ['aa', 'bb']
print(zip(s, t))  # 返回一个合并后的列表
for i in zip(s, t):
    print(i)
if isinstance(a_list, list):  # 判断字段是不是某一个数据类型
    print("yes")

# ===========================================================================================================
# 2.sys模块
print("*" * 100)
print(sys.argv)  # 返回参数列表，python xx.py aa > ['xx', 'aa']
# try:
#     print(sys.exit(2))  # 退出脚本返回状态 会被try截取
# except Exception as err:
#     print("yes", err)
print(sys.exc_info())  # 获取当前正在处理的异常类
print(sys.version, '|', sys.version.split()[0], sys.version_info, '|', sys.api_version)  # 获取python的系统版本号
print(sys.path)  # 返回模块的搜索路径，初始化时使用PYTHONPATH环境变量的值
print(sys.stdin, '|', sys.stdout, '|', sys.stderr)  # 标准输入,标准输出，错误输出
print(sys.modules)  # 返回系统导入的模块字段，key是模块名，value是模块
print(sys.platform, sys.winver)  # 返回操作系统的平台名称
print(sys.maxsize, sys.maxunicode)  # 最大值，最大的unicode值
print(sys.exec_prefix)  # 返回系统平台python安装的位置， C:\Program Files\AnChnet\python3.6
# print(sys.stdin.readline())  # 从标准输入读取一行
print(sys.stdout.write('hello world'))  # 屏幕上输出该字符和字符长度
# ===========================================================================================================
# 2.os模块
print("*" * 100)
import os

# os.popen('id').read()  # 执行系统命令并得到返回的结果
print(os.system)  # 得到返回状态，返回无法截取
print(os.name)  # 获取系统的用户名，linux/unix用户是'posix'
print(os.getenv(key='python'))
print(os.getcwd())  # 获取当前工作的路径
print(os.chdir('C:/'), os.getcwd())  # os.chdir() 改变当前工作路径
print(os.walk('C:/'), os.getcwd())  # 递归路径

# os相关的文件处理
# print(os.mkfifo('C://te.txt', 777), os.mknod('C://te.txt'))  # 创建系统命名管道并设置权限，创建系统节点
# print(os.remove("C://test.txt"), os.unlink("C://aaa.txt"))  #删除文件
# print(os.rename('C://test.txt', 'C://tes.txt'), os.renames('C://aaa.txt', 'C://aa.txt'))  # 重命名文件
print(os.stat('C://aa.txt'))  # 返回文件的信息
src = '/usr/bin/python'
dst = '/tmp/python'
# print(os.symlink(src, dst))  # 创建符号连接，linux系统下常用
# print(os.utime("C://aa.txt", (1330712280, 1330712292)))  # 用于设定系统文件最后的修改和访问时间
# print([i for i in os.walk("D://SoftWare")])  # 遍历目录树下的所有的文件名

# os 目录文件夹的处理
# print(os.chdir('D://SoftWare'))  # 改变当前文件的工作路径
# print(os.chroot('D://SoftWare/'))  #改变当前进程的根目录
print(os.listdir("D://SoftWare"))  # 列出指定目录的文件
print(os.getcwd())  # 返回当前工作目录
# print(os.mkdir('D://Test'), os.makedirs("D://Test/AAA/aa"))  # 创建目录，创建多层目录
# print(os.removedirs("D://Test/AAA/aa"), os.rmdir("D://Test/AAA/aa"))  # 删除目录，删除多层目录

# os访问权限
"""
os.F_OK: 作为access()的mode参数，测试path是否存在。
os.R_OK: 包含在access()的mode参数中 ， 测试path是否可读。
os.W_OK 包含在access()的mode参数中 ， 测试path是否可写。
os.X_OK 包含在access()的mode参数中 ，测试path是否可执行。
"""
# print(os.access("C://aa.txt", os.X_OK))  # 测试文件是否可以执行，
# print(os.chmod("C://aa.txt", 777))  # 改变文件的权限
# print(os.chown("C://aa.txt", ))  # 改变owner和groupID功能相同,但不会跟踪链接

# os.path 模块
# 1.查询
print(os.path.exists("C://aa.txt"), os.path.exists("D://Test"))  # 判断文件或者文件夹是否存在
print(os.path.isabs("C://aa.txt"))  # 判断路径是否为绝对路径
print(os.path.isdir("D://Test"), os.path.isfile("C://aa.txt"))  # 指定路径是否为目录/指定路径是否为文件
print(os.path.ismount("C://aa.txt"), os.path.islink("C://aa.txt"))  # 指定路径是否为挂载点/指定路径是否为一个符号链接
print(os.path.samefile("C://aa.txt", "C://aa.txt"))  # 判断两个路径名是否一致

# 获取信息
print(os.path.getsize("C://aa.txt"))  # 返回文件的字节大小
print(os.path.getatime("C://aa.txt"))  # 返回最近访问的时间
print(os.path.getmtime("C://aa.txt"))  # 返回最近文件修改的时间
print(os.path.getctime("C://aa.txt"))  # 返回文件的创建时间

# 分隔
print(os.path.basename("C://aa.txt"), os.path.basename(__file__), os.path.basename(sys.argv[0]))  # 去掉目录的路径返回文件名
print(os.path.dirname("C://aa.txt"))  # 去掉指定路径的文件名，返回路径
print(os.path.join(os.path.dirname("C://aa.txt"), os.path.basename(__file__)))  # 组合成一个新的路径
print(os.path.split("C://aa.txt"))  # 返回(dirname(),basename())元组
print(os.path.splitdrive("C://aa.txt"))  # 返回(drivename,pathname)元组
print(os.path.splitext("C://aa.txt"))  # 返回(filename,extension)元组

# ===========================================================================================================
# 3.shutil模块
print("*" * 100)
import shutil

# shutil可用于拷贝和移动文件
# print(shutil.copy("C://aa.txt", "C://aass.txt"))  # 文件的拷贝
# print(shutil.move("C://aass.txt", "D://aass.txt"))  # 文件的移动

# ===========================================================================================================
# 4.random模块
print("*" * 100)
# 随机生成整数或浮点数；随机取某个范围的整数，随机抽取不重复的元素或者列表
import random

print(random.random())  # 取随机浮点数
print(random.randint(1, 16))  # 随机取整数范围的数字
print(random.randrange(0, 999), random.randrange(88))  # 随机整数的范围

print(random.choice([1, 2, 3, 4]), random.choice((2, 6, 9)))  # 随机从列表/元组中去取一个元素
print(random.choices([1, 2, 3, 4]), random.choices((2, 6, 9)))  # 随机从序列中取一个元素的列表
print(random.sample([1, 2, 4, 8], 2), random.sample((1, 2, 4, 8), 2))  # 不重复抽取2个元素，并返回列表

# ===========================================================================================================
# 5.json模块
print("*" * 100)
import json

dict_str = ""
print(json.dumps(['foo', {'bar': ('baz', None, 1.0, 2)}]))
from io import StringIO

io = StringIO()
print(json.dump(['streaming API'], io))
print(io.getvalue())

# 紧凑编码
print(json.dumps([1, 2, 3, {'4': 5, '6': 7}], separators=(',', ':')))
# 美化输出
print(json.dumps({'4': 5, '6': 7}, sort_keys=True, indent=4), type({'4': 5, '6': 7}),
      type(json.dumps({'4': 5, '6': 7})))

# JSON 解码
print(json.loads('["foo", {"bar":["baz", null, 1.0, 2]}]'), type(json.loads('["foo", {"bar":["baz", null, 1.0, 2]}]')),
      json.dumps('["foo", {"bar":["baz", null, 1.0, 2]}]'), type(json.dumps('["foo", {"bar":["baz", null, 1.0, 2]}]')))

# ===========================================================================================================
# 6. time模块
print("*" * 100)
import time

print("当前时间戳：", time.time())  # 获取当前时间戳，1584934600.1377594
print(time.localtime(), time.localtime(time.time()), time.gmtime())  # 接收时间戳（1970纪元后经过的浮点秒数）并返回当地时间下的时间元组

print(time.strftime("%a %b %d %H:%M:%S", time.localtime()),
      time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()))  # 得到指定格式的时间
a = "Sat Mar 28 22:24:24 2016"
print(time.mktime(time.strptime(a, "%a %b %d %H:%M:%S %Y")))  # 根据fmt格式把一个时间字符串解析为时间元组

print(time.altzone)  # 返回格林威治西部的夏令时地区的偏移秒数。如果该地区在格林威治东部会返回负值（如西欧，包括英国）。对夏令时启用地区才能使用。
print(time.ctime(), time.asctime(time.localtime()),
      time.asctime(time.localtime(time.time())))  # 接受元组并返回(Mon Mar 23 17:05:40 2020)的字符串
# 7. datetime模块


# ===========================================================================================================
# 8. calendar模块
print("*" * 100)
import calendar

print(calendar.month(2020, 3))

print(calendar.firstweekday())  # 返回当前每周起日期的设置，默认情况下，首次载入calendar模块时返回0，即星期一
print(calendar.isleap(2020))  # 判断当前年份是不是闰年，是返回True，否则False
print(calendar.leapdays(2000, 2020))  # 返回两个年份之间的闰年总数

print(calendar.monthrange(2020, 3))  # 返回（6，31）6表示2020年3月份的第一天是周日，31表示3月份总共有31天

